/**
 * 计划功能
 * 1. 获取菜单数据
 * 2. 生成路由配置
 * 3. 代码生成
 *
 * date: 2018/07/04
 * author: XGP
 */
let http = require('http');
let querystring = require('querystring');
let fs = require("fs");
let path=require('path');
let DevConfig = require('./dev.env.js');
let generatorSettingFile = require('./table.setting')

let tableName = false;
process.argv.forEach(function (val, index, array) {
  let keyVal = val.split('=')
  let key = keyVal[0]
  let value = keyVal[1]
  if (key === 'tableName') {
    tableName = value
  }
});

let token;
let configObj = {
  hostname: DevConfig.HOST,
  port: DevConfig.PORT,
}
let beneform4jViewPath = path.join(__dirname, '../src/beneform4j/view');
let template = `
`;
function generatorTemplate(obj) {
  template = `

  <template>
  <div class="bf-commont-template">
    <div style="padding: 0 16px ;">
      <h3>${obj.title}</h3>
      <p>该页面代码已经自动生成，按照普通码 表增删改查 为基础生成模板</p>
      <p>生成代码对应的 vue 文件路径：${obj.vueFilePath}</p>
      <el-alert title="注意：表格内数据为模拟数据, 如果数据格式不对，请先进行格式转换。 模拟数据文件路径：src/mock/demo.js" type="warning"> </el-alert>
    </div>

    <div class="clearfix bf-top-button">
      <div class="float-l">
        <el-button @click="showAdd" type="primary">新增</el-button>
      </div>
      <div class="float-r">
        <div class="float-l">
          <el-input
            placeholder="请输入搜索内容"
            prefix-icon="el-icon-search"
            v-model="searchData"
            @keyup.enter.native="quickSearch"
          ></el-input>
        </div>
        <div class="float-l padding-l">
          <el-button @click="showSearch" type="primary">高级筛选</el-button>
        </div>
      </div>
    </div>

    <bf-table
      :data="listData"
      :setting="setting"
      :rowAction="rowAction"
      @pageChange = "pageChange"
      :editRules = "editRules"
      ref="table"
    ></bf-table>

    <bf-table-detail :title="'详情展示'" :editForm='setting' ref='detailRef' ></bf-table-detail>
    <bf-table-edit :title="'编辑'" :editForm='setting' ref='editRef' @formSubmit='editSubmit' :editRules="editRules"></bf-table-edit>
    <bf-table-edit :title="'新增'" :editForm='setting' ref='addRef' @formSubmit='addSubmit' :editRules="editRules"></bf-table-edit>
    <bf-table-search :title="'搜索'" ref="searchRef" :editForm="setting" @formSubmit='searchSubmit'></bf-table-search>
  </div>
</template>

<script>
import request from '@/utils/request'
import { getListApi, editItemApi, deleteItemApi, addItemApi } from './api'
${
  tableName?"import { setting, rule } from './setting'":''
}
export default {
  data() {
    return {
      searchData: '',
      listData: {
      },
      searchParams: { // 获取 list 搜索条件，分页
        page: 1
      },
      rowAction: [
        {
          label: '详情',
          click: (item) => {
            this.$refs.detailRef.show(item.scope.row)
          }
        },
        {
          label: '编辑',
          click: (item) => {
            this.$refs.editRef.show(item.scope.row)
          }
        },
        {
          label: '删除',
          click: (item) => {
            this.$confirm('删除该条记录, 是否继续?', '提示', {
              confirmButtonText: '确定',
              cancelButtonText: '取消',
              type: 'warning'
            }).then(() => {
              this.$message({
                type: 'success',
                message: '删除成功'
              })
            }).catch(() => {
              this.$message({
                type: 'info',
                message: '已取消操作'
              })
            })
          }
        }
      ],
      ${tableName?`setting:setting,`:`
      setting: [
        {
          field: 'name',
          title: '用户名称',
          type: 'text',
          searchable: true
        },
        {
          field: 'roleName',
          title: '用户角色',
          type: 'text',
          searchable: true
        },
        {
          field: 'introduction',
          title: '用户介绍',
          type: 'text'
        },
        {
          field: 'avatar',
          title: '用户连接',
          type: 'text'
        }
      ],`}
      ${tableName?'editRules: rule':
      `
      editRules: {
        name: [
          { required: true, message: '请输入用户名称', trigger: 'blur' },
          { min: 3, max: 20, message: '长度在 3 到 20个字符', trigger: 'blur' }
        ],
        roleName: [
          { required: true, message: '请输入用户角色', trigger: 'blur' },
          { min: 3, max: 20, message: '长度在 3 到 20个字符', trigger: 'blur' }
        ]
      }
    `}}
  },
  mounted: function() {
    this.searchList()
  },
  methods: {
    searchList() {
      let params = this.searchParams
      request({
        url: '/demo/demo/demo',
        method: 'get',
        params: params
      }).then((response) => {
        this.listData = response
      })
      /** getListApi(params).then(response => {
        if (response.success) {
          this.listData =response
        }
      }) **/
    },

    showSearch() { // 展示高级搜索form
      this.$refs.searchRef.show()
    },
    searchSubmit(form) {  // 高级搜索提交
      this.searchParams.page = 1
      this.searchParams.planName = form.planName

      this.searchList()
      this.$refs.searchRef.hiden()
    },
    showAdd() { // 展示新增form
      this.$refs.addRef.show({})
    },
    addSubmit(form) { // 新增提交
      console.log(form)
    },
    editSubmit(form) { // 编辑提交
      console.log(form)
    },
    quickSearch() { // 快捷搜索
      this.searchParams.page = 1
      this.searchParams.planName = this.searchData
      this.searchList()
    },
    pageChange(pageObj) { // 分页处理
      this.searchParams.page = pageObj.page
      this.searchParams.pageSize = pageObj.pageSize
      this.searchList()
    },
  }
}
</script>

<style scoped>

</style>
  `;
}
/**
 * 1.登录获取token
 * 2.使用token 获取菜单数据
 * 3.将菜单数据写入到menu.json 文件
 * 4.处理菜单数据
 */
// login();

/**
 * 登录
 */
function login(){
  const postData = querystring.stringify({
    userId: 'dev',
    userPwd: '111111'
  });

  const options = {
    hostname: configObj.hostname,
    port: configObj.port,
    path: '/beneform4j-webapp-angular/login',
    method: 'POST',
    headers: {
      'Content-Type': 'application/x-www-form-urlencoded',
      'Content-Length': Buffer.byteLength(postData)
    }
  };

  const req = http.request(options, (res) => {
    res.setEncoding('utf8');
    res.on('data', (chunk) => {
      let data = JSON.parse(chunk);
      console.log('token:  '+ data.token)
      token = data.token;
      getMenu();
    });
    res.on('end', () => {
      console.log('login success 100%');
    });
  });

  req.on('error', (e) => {
    console.error(`login http error: ${e.message}`);
  });
  // 写入数据到请求主体
  req.write(postData);
  req.end();
}

/**
 * 新vue平台中，新获取菜单接口，不需要登录即可获取所有菜单
 * 权限需要在登录后获取可登录菜单配置
 */
getMenu();
/**
 * 获取菜单数据
 */
function getMenu(){
  let chunks = '';
  const options = {
    hostname: configObj.hostname,
    port: configObj.port,
    path: '/autumn-admin/v1/code/foreground/menus',
    method: 'GET',
    headers: {
      'Content-Type': 'application/x-www-form-urlencoded',
      'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/67.0.3396.87 Safari/537.36'
    }
  };
  console.log(options)
  console.log('http请求获取所有菜单配置');
  const req = http.request(options, (res) => {
    res.setEncoding('utf8');
    res.on('data', (chunk) => {
      chunks += chunk;
    });
    res.on('end', () => {
      console.log('所有菜单配置获取完成 success: 100%');
      // console.log(chunks)
      fs.writeFile(__dirname + '/menu.json', chunks, (err) => {
        if(err) {
          console.error('将菜单配置写入menu.json 文件: error' + err);
        } else {
          console.log('将菜单配置写入menu.json 文件 success: 100%');
        }
      })
      dealMenus();
    });
  });

  req.on('error', (e) => {
    console.error(`http请求获取所有菜单配置 error: ${e.message}`);
  });
  req.end();
}

/**
 * 对获取的tree json 数据进行处理，生成vue touter 配置文件
 * 递归处理menus tree数据
 */
function dealMenus() {
  let menusData;
  fs.readFile(__dirname + '/menu.json','utf8',function (err, data) {
    if (err) {
      console.log('读取、解析menu.json文件 error:'+err);
    } else {
      menusData = JSON.parse(data);
      console.log('读取、解析menu.json文件 success 100%');
      // 递归处理生成vue 页面模板文件
      dealMenusItem(menusData.data);
      // 生成vue 路由配置文件
      generatorVueRouterFile(menusData.data);
    }
  });

  function dealMenusItem(menusItem) {
    menusItem.forEach((v) => {
      // console.log(v)
      if (v.children) {
        dealMenusItem(v.children)
      } else {
        if (v.leaf) {
          if (v.url) {
            generatorVueComponent(v);
          } else {
            /**
             * 当url 为空时特殊处理 TODO:
             */
          }
        }
      }
    })
  }
}

/**
 * 1. 生成vue 文件
 * 2. 生成vue 路由
 * 生成对应的vue 路由
 * @param {*单个菜单(后端配置数据)} item
 */
function generatorVueComponent(item) {
  // console.log(item);
  let pathArr = [];

  item.url.split('/').forEach((v) => {
    pathArr.push(v)
  })
  let len = pathArr.length;
  let filePath;
  pathArr.forEach((menusItemPath, index) => {
    /**
     * 判断需要生成的vue模板文件是否已经存在
     */
    let currenPath = pathArr.slice(0,index+1).join('/');
    let newJoinPath = path.join(beneform4jViewPath,'./'+currenPath);
    let isExitFile = fs.existsSync(newJoinPath);
    // console.log(newJoinPath)
    // console.log(isExitFile)
    if (isExitFile) {
      // 存在该文件夹
    } else {
      /**
       * 不存在该文件夹，2种情形
       * 1. 为最后一个目录path
       * 2. 不是最后一个目录paht
       */
      if (len === index+1) {
        // 最后一级 path
        let vueFilePath = path.join(beneform4jViewPath, './'+ item.url +'.vue');
        // console.log(vueFilePath);
        // 判断是否存在该文件
        let isExitVueFile = fs.existsSync(vueFilePath);
        // console.log(isExitVueFile);
        if (isExitVueFile) {
          // 已经存在，不做处理
        } else {
          // 不存在该vue 文件，生成vue文件
          generatorFile(vueFilePath);
          if (tableName) {
            // 生成api.js 文件
            let len = pathArr.length
            let settingPath = pathArr.slice(0,len-1).join('/');
            let settingFilePath = path.join(beneform4jViewPath, settingPath + '/setting.js');
            generatorSettingFile(tableName, settingFilePath);
          }
        }
      } else {
        // 不存在该文件夹， 新建文件夹
        fs.mkdirSync(newJoinPath);
      }
    }
    function generatorFile(vueFilePath) {
        fs.open(vueFilePath, 'w', (err, fd) => {
          if (err) {
            return console.log('生成 '+ vueFilePath +'模板文件 error:' + err);
          } else {
            let htmlObj = {
              title: item.text, // 模板文件标题
              vueFilePath: vueFilePath // 模板文件中提示的文件路径
            }
            generatorTemplate(htmlObj);
            fs.writeFile(fd, template, function(err){
                if (err){
                  return console.log('生成 '+ vueFilePath +'模板文件 error:' + err);
                }
                console.log('生成 '+ vueFilePath +'模板文件 success 100%');
            });

            // 关闭文件
            fs.close(fd, function(err){
              if (err){
                return console.log('关闭 '+ vueFilePath +'模板文件 error:' + err);
              }
            });
          }
        });
        // 生成api.js 文件
        let len = pathArr.length
        let apiPath = pathArr.slice(0,len-1).join('/');
        let apiFilePath = path.join(beneform4jViewPath, apiPath + '/api.js');
let apiFileTemplate = `
/**
 * name: 菜单名称
 * date: ${new Date().toLocaleDateString()}
 * author: 开发人员名称
 * des: 页面描述
 * 规范：
 *  1 请完善以上注释：菜单名称、开发人员名册（使用英文，可中文名缩写）、页面描述
 *  1 HTTP 请求函数名称使用Api 作为后缀，例如" getListApi "
 *  2 PUT 请求方式使用 data 方式(请求体)传输参数， 例如： editItemApi 函数中使用put 请求方式，参数"data: params"
 *  3 每个请求方式请完善注释：例如：“获取列表数据、修改单条数据、删除单条数据、新增单条数据”
 *  4 查询使用get 请求方式、新增使用 post 请求方式、删除使用 delete 请求方式、修改使用 post 请求方式
 */

import request from '@/utils/request'

/**
 * 获取列表数据
 */
export function getListApi(params) {
  return request({
    url: '/employeeapplys/findStatusCount',
    method: 'get',
    params: params
  })
}

/**
 * 修改单条数据
 */
export function editItemApi(params) {
  return request({
    url: '/employeeapplys/updateBackDelay',
    method: 'put',
    data: params
  })
}

/**
 * 删除单条数据
 */
export function deleteItemApi(id) {
  return request({
    url: '/recruitreqs/delete/' + id,
    method: 'delete'
  })
}

/**
 * 新增单条数据
 */
export function addItemApi(params) {
  return request({
    url: '/recruitreqs/insert',
    method: 'post',
    data: params
  })
}
`;
        fs.open(apiFilePath, 'w', (err, fd) => {
          if (err) {
            return console.log('生成 '+ vueFilePath +'模板文件 error:' + err);
          } else {
            fs.writeFile(fd, apiFileTemplate, function(err){
                if (err){
                  return console.log(err);
                }
            });
            // 关闭文件
            fs.close(fd, function(err){
              if (err){
                return console.log(err);
              }
            });
          }
        });
    };
  })
}
/**
 * 生成vue router 配置文件
 * @param {*} item
 */
let routerConfigFileStart = `
import Layout from '@/views/layout/Layout'
const _importBf = require('./_import_beneform4j')
const generatorRouter =
`;
let routerConfigFileEnd = `
export default generatorRouter
`;
/**
 * 数据格式化，格式为vur router 配置格式
 * @param {*} item
 */
function generatorVueRouterObj(item){
  item.meta = {
    icon: item.icon,
    title: item.text,
    roles: ['admin']
  };
  item.name = item.id;
}
/**
 * 生成 router 配置文件
 * @param {*} menuObj
 */
function generatorVueRouterFile(menuObj){
  // console.log(JSON.stringify(menuObj))
  let str = JSON.stringify(menuObj);
  let template = `export const generatorRouter = `+ str.replace(/{/g,'{\r\n');
  let filePath = path.join(__dirname, '../src/beneform4j/router');

  fs.open(filePath + '/menu.router.js' , 'w', (err, fd) => {
    if (err) {
      return console.log('创建 vue router 配置文件失败 error:' + err)
    }
    fs.writeFile(fd, template, function(err){
      if (err){
        return console.log("生成 vue router 配置文失败 error:"+err);
      }
      // 关闭文件
      fs.close(fd, function(err){
        if (err){
          return console.log("关闭 vue router 配置文失败 error:"+err);
        }
      });
      console.log("创建、生成 vue router 配置文件 success 100%");
    });
  })
}
